perm filename DEVIND.SAI[S,HE]2 blob
sn#652457 filedate 1982-04-13 generic text, type C, neo UTF8
COMMENT ⊗ VALID 00013 PAGES
C REC PAGE DESCRIPTION
C00001 00001
C00003 00002 ENTRY DDDEV,FILDEV,XGPDEV,GRNDEV,DOVDEV,CANDEV,PICDEV,SYNDEV,LINE,SEE,SETCLR
C00007 00003 INTEGER PROCEDURE NEWPIC(INTEGER HEIGHT,WIDTH,BITS)
C00008 00004 INTERNAL INTEGER PROCEDURE DDDEV
C00009 00005 INTERNAL INTEGER PROCEDURE XGPDEV
C00011 00006 INTERNAL INTEGER PROCEDURE DOVDEV
C00012 00007 INTERNAL INTEGER PROCEDURE SYNDEV
C00013 00008 Routines for doing picture graphics. These were stolen with minor
C00015 00009 INTERNAL PROCEDURE LINE(INTEGER D REAL X1,Y1,X2,Y2)
C00021 00010 INTERNAL PROCEDURE DOT(INTEGER D REAL X,Y)
C00030 00011 INTERNAL PROCEDURE SEE(INTEGER D)
C00039 00012 INTERNAL PROCEDURE SETCLR(INTEGER C)
C00040 00013 END "DEVIND"
C00041 ENDMK
C⊗;
ENTRY DDDEV,FILDEV,XGPDEV,GRNDEV,DOVDEV,CANDEV,PICDEV,SYNDEV,LINE,SEE,SETCLR;
COMMENT These routines are for the device-independent graphics package.;
BEGIN "DEVIND"
COMMENT For ADDIEL;
REQUIRE "DEVINS.REL[GRA,AAM]" LOAD_MODULE;
COMMENT For PIXDIM,MAKPIX,LNBY et al;
REQUIRE "PIXHDR.SAI[VIS,HPM]" SOURCE_FILE;
COMMENT For GDDCHN,SHOWA,SYNMAP;
COMMENT REQUIRE "DDHDR.SAI[GRA,HPM]" SOURCE_FILE;
COMMENT These defn's here 'cause we redefine LINE etc.;
REQUIRE "DDSAI[gra,hpm]" LIBRARY;
REQUIRE "DDFAI[gra,hpm]" LIBRARY;
EXTERNAL BOOLEAN PROCEDURE MAPMON(REAL GAMMA; INTEGER RESET(0));
external integer PROCEDURE SYNMAP(INTEGER ORD,reset(0));
EXTERNAL PROCEDURE SHOWA(INTEGER CHAN,console(-1)); comment add chan to console;
EXTERNAL INTEGER PROCEDURE GDDCHN(INTEGER CHAN(-1));
COMMENT For FILE_LINE,FILE_SEE,FILE_DOT;
REQUIRE "FILHDR.SAI[GRA,AAM]" SOURCE_FILE;
COMMENT For GRNLIN,GRNDOT;
REQUIRE "GRNGRA.SAI[GRA,AAM]" SOURCE_FILE;
COMMENT Device identifiers;
DEFINE DD = 1,
FILE = 2,
XGP = 3,
GRINNELL = 4,
DOVER = 5,
CANON = 6,
PICTURE = 7,
SYNTHESIZER = 8;
DEFINE CRLF = "'15&'12";
COMMENT Color of graphics;
REAL COLOR;
COMMENT Device table;
DEFINE DEVTBSIZE = 100;
INTEGER ARRAY DEVTAB[0:DEVTBSIZE-1];
INTEGER DEVUSED;
COMMENT Grinnell line buffer;
DEFINE GLBUFSIZE = 100;
REAL ARRAY LINEBUF[0:GLBUFSIZE-1,1:4];
INTEGER GLBUF;
COMMENT Grinnell dot buffer;
DEFINE GDBUFSIZE = 100;
REAL ARRAY DOTBUF[0:GDBUFSIZE-1,1:2];
INTEGER GDBUF;
PROCEDURE DENTER(INTEGER NUM);
COMMENT Make an entry into the device table at the current position.;
BEGIN "DENTER"
IF DEVUSED > DEVTBSIZE THEN PRINT("Device table overflow...too many graphics"&
" output devices"&CRLF)
ELSE
BEGIN
DEVTAB[DEVUSED] ← NUM;
DEVUSED ← DEVUSED + 1
END
END "DENTER";
INTEGER PROCEDURE NEWPIC(INTEGER HEIGHT,WIDTH,BITS);
COMMENT Make a new picture which is HEIGHT by WIDTH and has BITS bits per
pixel. The routine returns the address of the picture.
NOTE that this will quite likely have to be changed when multiple languages are
accomodated.;
BEGIN "NEWPIC"
EXTERNAL INTEGER PROCEDURE ARMAK(INTEGER LB,UB,DIMS);
INTEGER PICADDRESS;
PICADDRESS ← ARMAK(0,PIXDIM(HEIGHT,WIDTH,BITS),1);
MAKPIX(HEIGHT,WIDTH,BITS,MEMORY[PICADDRESS]);
RETURN(PICADDRESS)
END "NEWPIC";
INTERNAL INTEGER PROCEDURE DDDEV;
BEGIN "DDDEV"
COMMENT Initialize a DD channel.;
INTEGER C,D;
D ← DEVUSED;
DENTER(DD); COMMENT Device table contains "DD";
DENTER(NEWPIC(480,512,1)); COMMENT and buffer address (buffer is 1-bit pic);
DENTER(-2); COMMENT channel in use (-2 means none picked yet);
RETURN(D)
END "DDDEV";
INTERNAL INTEGER PROCEDURE FILDEV(INTEGER IOCHAN);
BEGIN "FILDEV"
COMMENT Initialize a file.;
INTEGER D;
D ← DEVUSED;
DENTER(FILE); DENTER(IOCHAN); COMMENT Device table contains "FILE" and io chan;
RETURN(D)
END "FILDEV";
INTERNAL INTEGER PROCEDURE XGPDEV;
COMMENT Initialize the XGP for output.;
BEGIN "XGPDEV"
INTEGER D;
PRINT("Sorry. XGP graphics are not currently implemented."&CRLF);
D ← DEVUSED;
DENTER(XGP); COMMENT Device table contains "XGP";
RETURN(D)
END "XGPDEV";
INTERNAL INTEGER PROCEDURE GRNDEV;
COMMENT Initialize the Grinnell for output...no big deal yet.;
BEGIN "GRNDEV"
INTEGER D;
PRINT("NOTE: Grinnell is currently single-user mode...take your chances."&CRLF);
D ← DEVUSED;
DENTER(GRINNELL); COMMENT Device table contains "GRINNELL";
DENTER(1); COMMENT and channel no.;
DENTER('7777); COMMENT and subchannel mask;
RETURN(D)
END "GRNDEV";
INTERNAL INTEGER PROCEDURE DOVDEV;
COMMENT Initialize dover for graphics.;
BEGIN "DOVDEV"
INTEGER D;
PRINT("Sorry. Dover output is not currently implemented."&CRLF);
D ← DEVUSED;
DENTER(DOVER);
RETURN(D)
END "DOVDEV";
INTERNAL INTEGER PROCEDURE CANDEV;
COMMENT Initialize Canon for graphics.;
BEGIN "CANDEV"
INTEGER D;
PRINT("Sorry. Canon output is not currently implemented."&CRLF);
D ← DEVUSED;
DENTER(CANON);
RETURN(D)
END "CANDEV";
INTERNAL INTEGER PROCEDURE SYNDEV;
COMMENT Initialize the synthesizer for graphics.;
BEGIN "SYNDEV"
INTEGER D;
D ← DEVUSED;
DENTER(SYNTHESIZER); COMMENT Device table contains "SYNTHESIZER";
DENTER(NEWPIC(480,512,8)); COMMENT and the address of the 8-bit pic buffer;
RETURN(D)
END "SYNDEV";
INTERNAL INTEGER PROCEDURE PICDEV(REFERENCE INTEGER PIC);
COMMENT Make graphics go into an incore picture;
BEGIN "PICDEV"
INTEGER D;
D ← DEVUSED;
DENTER(PICTURE); DENTER(LOCATION(PIC));
RETURN(D)
END "PICDEV";
COMMENT Routines for doing picture graphics. These were stolen with minor
modification, from H. P. Moravec.;
PROCEDURE THIN(INTEGER PIC; REAL X1,Y1,X2,Y2);
BEGIN "THIN"
REAL LEN,DX,DY; REAL I,MODHALF; INTEGER I2LEN;
COMMENT Get position of endpoints in pixel coords.;
X1←(MEMORY[PIC+LNBY]-1.0)*X1;
Y1←(MEMORY[PIC+PCLN]-1.0)*Y1;
X2←(MEMORY[PIC+LNBY]-1.0)*X2;
Y2←(MEMORY[PIC+PCLN]-1.0)*Y2;
COMMENT LEN is length of line to draw, and MODHALF is LEN mod 0.5;
DX←X2-X1; DY←Y2-Y1;
LEN←SQRT(DX↑2+DY↑2);
I2LEN ← LEN*2;
MODHALF ← (LEN*2 - I2LEN)/2;
DX←DX/LEN; DY←DY/LEN;
COMMENT Plot points at each half-pixel with half brightness;
FOR I←0 STEP 0.5 UNTIL LEN DO
ADDIEL(MEMORY[PIC],Y1+DY*I,X1+DX*I,COLOR/2);
COMMENT And plot the last point with the appropriate brightness;
ADDIEL(MEMORY[PIC],Y2,X2,MODHALF*COLOR);
END "THIN";
INTERNAL PROCEDURE LINE(INTEGER D; REAL X1,Y1,X2,Y2);
COMMENT Draw a line from x1,y1 to x2,y2 in normalized device coordinates on
device D. ;
BEGIN "LINE"
CASE DEVTAB[D] OF BEGIN "DEVICE CASES"
[FILE] BEGIN COMMENT Output the calling params;
INTEGER C;
C ← DEVTAB[D+1];
WORDOUT(C,FILE_LINE);
WORDOUT(C,X1);
WORDOUT(C,Y1);
WORDOUT(C,X2);
WKRDOUT(C,Y2)
END;
[XGP]; COMMENT Unimplemented;
[GRINNELL] BEGIN COMMENT Buffer a set of lines for CR's rtn.;
LINABUF[GLBUF,1] ← X1;
LINABUF[GLBUF,2] ← Y1;
LINABUF[GLBUF,3]← X2;
↓LINABUF[GLBUF,4] ← Y2;
GLBUF ← GLBUF+1;
IF GLBUF > GLBUFSIZA THEN¬
BEGIN
GRNLINE(D,LINEBUF,GLBUFSIZE);
GLBUF ← 1
END
END;
[DOVER]; COMMENT Unimplemented;
[CANON]; COMMENT Unimplemented;
[DD] COMMENT Draw a thin line;
[PICTURE]
[SYNTHESIZER] COMMENT SAIL bug means SYNTHESIZER last;
THIN(DEVTAB[D+1],X1,Y1,X2,Y2)
END "DEVICE CASES"
END "LINE";
INTERNAL PROCEDURE DOT(INTEGER D; REAL X,Y);
COMMENT Make a point on device D. at x,y;
BEGIN "DOT"
CASE DEVTAB[D] OF BEGIN "DEVICE CASES"
[FILE] BEGIN COMMENT Output the calling params;
INTEGER CHAN;
CHAN ← DEVTAB[D+1];
WORDOUT(CHAN,FILE_DOT);
WORDOUT(CHAN,X);
WORDOUT(CHAN,Y)
END;
[XGP]; COMMENT Unimplemented;
[GRINNELL] BEGIN COMMENT Buffer a set of dots for CR's rtn.;
DOTBUF[GDBUF,1] ← X;
DOTBUF[GDBUF,2] ← Y;
GDBUF ← GDBUF+1;
IF GDBUF > GDBUFSIZE THEN
BEGIN
GRNDOT(D,DOTBUF,GDBUFSIZE);
GDBUF ← 1
END
END;
[DOVER]; COMMENT Unimplemented;
[CANON]; COMMENT Unimplemented;
[DD] [SYNTHESIZER] COMMENT Put an interpolated dot into the
picture.;
ADDIEL(MEMORY[DEVTAB[D+1]],Y*479.0,X*511.0,COLOR);
[PICTURE] BEGIN COMMENT Another interpolated dot...;
INTEGER PIC;
PIC ← DEVTAB[D+1];
ADDIEL(MEMORY[PIC],Y*(MEMORY[PIC+PCLN,INTEGER]-1.0),
X*(MEMORY[PIC+LNBY,INTEGER]-1.0),COLOR)
END
END "DEVICE CASES"
END "DOT";
INTERNAL PROCEDURE SEE(INTEGER D);
COMMENT Make graphics visible on device D.;
BEGIN "SEE"
COMMENT DD buffer has 480 lines, each line has 16 graphics words, a line
select, and an execute. The whole picture has 2 extra words: a channel/mode
select and a halt.;
DEFINE DDBUFSIZE = "480*18+2"; COMMENT DD Buffer size;
INTEGER ARRAY DDBUF[0:DDBUFSIZE-1];
OWN INTEGER ARRAY CTLBLK[0:3];
INTEGER BUFPTR;
COMMENT Put a word into the DD buffer;
PROCEDURE INSERT(INTEGER WORD);
BEGIN "INSERT"
DDBUF[BUFPTR] ← WORD;
BUFPTR ← BUFPTR + 1
END "INSERT";
CASE DEVTAB[D] OF BEGIN "DEVICE CASES"
[FILE] WORDOUT(DEVTAB[D+1],FILE_SEE); COMMENT Output the calling params;
[XGP]; COMMENT Unimplemented;
[GRINNELL] BEGIN COMMENT Flush all buffers associated with
the Grinnell;
COMMENT Flush line buffer;
GLBUF ← GLBUF-1;
IF GLBUF > 0 THEN
GRNLINE(D,LINEBUF,GLBUF);
GLBUF ← 1;
END;
[DOVER]; COMMENT Unimplemented;
[CANON]; COMMENT Unimplemented;
[DD] BEGIN "DD OUTPUT" COMMENT Make a DD instruction set from a
one-bit picture.;
INTEGER CHAN,BP,I,J,WORD,SC;
INTEGER LINE,STARTLINE;
COMMENT Start by getting output channel and setting mode.;
IF DEVTAB[D+2] = -2 THEN DEVTAB[D+2] ← GDDCHN; COMMENT -2 means none yet;
CHAN ← DEVTAB[D+2];
BUFPTR ← 0;
COMMENT -1 channel means our own, DD can't use 0;
SC ← IF CHAN < 0 THEN 0 ELSE IF CHAN = 0 THEN '40 ELSE CHAN;
INSERT((SC ROT -8) + (2 ROT -27) COMMENT Select channel;
+ (7 ROT -16) + (1 ROT -30) COMMENT Set functions: dark back,
write enb, graphic mode;
+ (2 ROT -33) COMMENT no-op (sel. ch. 0);
+ 4); COMMENT Command word opcode;
COMMENT Now display all the lines in 4 sets. This is the only way the
timing will work properly on the Datadisc.;
FOR STARTLINE ← 0 STEP 1 UNTIL 3 DO
FOR LINE ← STARTLINE STEP 4 UNTIL 479 DO
BEGIN "LINE OUTPUT"
INSERT(((LINE LSH -4) ROT -8) + (4 ROT -27) COMMENT Hi line ad;
+ ((LINE LAND '17) ROT -16) + (5 ROT -30) COMMENT Lo ad;
+ (1 ROT -24) + (3 ROT -33) COMMENT Select col 1;
+ 4); COMMENT Command word;
COMMENT For each line, use a byte pointer to extract 32-bit hunks
and put them into the DD buffer. One line has 16 such
hunks.;
BP ← POINT(4,MEMORY[MEMORY[DEVTAB[D+1]+LINTAB+LINE]],-1);
WORD ← 0;
FOR I ← 1 STEP 1 UNTIL 16 DO BEGIN "GET ONE WORD"
FOR J ← 1 STEP 1 UNTIL 8 DO
WORD ← (WORD LSH 4) + ILDB(BP);
INSERT((WORD LSH 4) + 2) COMMENT 2 means graphic wrd;
END "GET ONE WORD";
COMMENT And now an execute command to draw the line;
INSERT('0224) COMMENT exec. and 2 sel chn;
END "LINE OUTPUT";
COMMENT Finish up by putting in a halt instruction.;
INSERT(0);
COMMENT Now run the datadisc program and show The resultto the user.;
CTLBLK[0] ← LOAATION(DDBUF[0]);
ATLBLK[1] ← DDBUFSIZE;
QUICK_CODE
∩@@A!∂%≠ @f1β!→¬1↔6a~l∪π∂≠5≥(AQQChOLAae←9←k]Gα+⊃↓
$"VB≥⊃X4(ε,r⊃l4PJN">< "∞"q$4 α↓↓α⊗t!↓
∩ ∧∧`:5∀∃*DL¬FEβE)alS*$"iRm"a.H!"cdS⊂⊃)lS*$⊂'Uj("jλ∧agfSbg*⊂∃44yP~yP0@≠5z⊂ ,ike The DD, bu@P@qp\l~∀4PJ&*R,:⊗Iα≤Bε92∃↓2%2Rb∀MEIT
≤5Jtm∀G1PPL→jD,<Z ∧dLhUE≥$~*DdLhW0hPβ"H∧∧λ⊂siY13U∧
⎇_<ND_↑(∞<αz24[3P:xλ90 deo intensi@QrAiC YJAC9HAOe¬EES]≤AGQC9]KYfl~∀∪'e≥≠β `XJBαId4*≤z6&⊗u!α∨K∂K∂?∪Ls⊂~ε]xFN⊗≤↑2π&
~2εf≥lS@4λ∪0* 3sBε∃L
.aQ@∧a$U⊂/P_∞FE∧kR$f"P
!d gλ/P)lS&`h∀⊂αIT)) ≠ -⊃ DG BEG@∪≤α↓α>V%αVQα|r∃α
M! (,∞&NwEλJ∞Y<_.-8π3@ bit ",bi`(0@A←\↓GQC]9KX@D1`∂g≠nA#M!%!≥)→
E⊂Id4(J↓↓α
,2BRI¬y↓AlhP%↓↓∧J2N⊗∃!!"∞D
9αJ⎇!↓5aJ↓-↓∧ λ
)uλ&&j(λ∧∧λλ⊂iYαfbg∃⊂)r`,ect Cha`≥]∃Xv~∀$∩V@Pβ9αJ>"↓5EYJ↓-↓∧∧
)uλ&6λ∧P⊂λ⊂⊂⊂⊂λ!`∂MMEH
(AMKhAMU]GiSα{;Mi∧#πK4λ&∞≡5APPH⊃⊃⊂HHα(λ∧∞|Z0~→P2w1⊂3y0\44qP≠wr2]CE + (2 RMPλ@ZLfR@@@@@@@@@@@@@@@@@A
_∞ ,XYe"εmuV␈α¬∞6.bdλλm¬H
'⊃"B"%4
.d∧λλλ∧∧λλλ∧∧λλλ∧∧λλλ∧∧λλλ∧∧λλλλdπEMEL¬(Aπα{77πv!βO?⊗!β/C≤¬v&+αc"AQHλλ∧∧λλ⊂i@d¬MENT @≥←β9β∪'≥β3πe∧∧⊗f@λ≥~T≠~0↔→yP4`. 4 sEts ≤@↓)QSF↓SfAi!JA←]1rAoCdAiQJ4⊂λ%↓αβS']_L@P;t`,l wo@IP
βC⊗{C↔Kdπ∩ε↑dλ
(⊃_.L9~0→XU_
FLπ$A≥"εJRdJ0∀(⊂∂P⊂)`∀EP 1 ULTAL 3 DO
λ∧∩@@@@@A→_∞IαdJ0∀(⊂∂P∀h∧ARTLINE SP α↓QαVu"& "∧¬≠NP"'FBα ∩@A¬∂%_ ↓
dJ0∀(∪u*J∃0
"
∩∩@@@@A∪≥≤*JQ¬
I3Q( Jp∧⊂⊗M∀P ∩OT ~@@¬∩αZ¬
∧
Su⊂Y≠TP⊂βH∂6l*0∃"
∩ε@~;Y$9∞c!∧@ +PQ2Lr∃αH→d"αv⊂
e∀∀Su∧¬,-J$¬h
~H)'j -30) @π⊂≡YXT`*λ∪⊂↔H0r≥FBα ↓ +PbA∀zQ↓T∧@~
P⊂ (3 ROT -3#) CLπ≠≠9(A'Kαc↔∂Q∧∧6}b∧⊂∞aQ@∧DDH⊂⊂⊂∃H~⊂]@ @π⊂≡⊗l*0∃"λ8m]8;Y∧∞{|YπFE∧DH⊂⊂!gSd¬ENT @
@?α λ\8z≥M8π2Vλ84qeH8¬p @QQJACAae@?αλM≤=→(-=_ P_w2⊂ 0lh∂`~(∩∩%α↓βC#,¬RεNβ]≠d∞~→(λHα⊂1:Y32yπλ⊂*44\β is all @⊃←]JA¬`∂OWnK;≥β∞p4(⊃⊃∩αα∧ε⊗X4z⊂ 0icte@IJT`,hP$%↓α↓↓↓↓∧∩Aα⎇¬α0≤LhAβBdXYTm∃≠9T,@3tV+_⊃0*⊂a)b+1]+LILTAB-→∪≥u:P⊃T∧ ∀Nβ
COMIENT CraycodiNdεA[←α#'6≤Z2π&
_d
~;Y'P⊂&`TeP/PP")dλ∀≠Va∩h∧ ∩v4⊂∩%α↓↓↓↓ααV =(@λtλ
DPβH∂≠≠∃_
Qααyu∀α∞⎇⊗f@λ_8l>;=;≡→(⊂$|X<
8h⊂≠[y2≥FB∧@P⊂λ⊂⊂⊂⊂⊃'i⊂$H/P_@∀j"h⊂P*g*∩d∧ 16 DG BEG@∪≤4∀∩∩∩@A
∨HA∀A≡bA'$*A↓E¬*:R&b↓MIα$x%↓↓∧~0≤@313JD⊂8pn]=;⊂⊂]2P;w\2≥FEαD@ WH∂%λ↓>@Q<zJ⊃αe~!↓EJ↓,4(HH$%↓α↓↓↓↓DJ→↓"Lb∩ "∃↓%αH→d"∧X~4ZJβ0βα¬IλT`$(⊃)Jq(¬↔c"B!⊃(λλ →β)bi∃∀∀ ↔ORD LSH 4) + 2) COMIENT 2 means gpaphic wrd;
EL@;
AKMMEL¬(Aβ9HA]←\ACLA∃qKGkQJAG←5[CMHαβS :N&∂:∞Mε*εM≥f+XQ!⊂Jα∧∧ααα →e≤-*Eα;β&"BJα∧∧ααα∧∧ααα∧∧ααα∧∧ααα∧λ4`9αfbg∃⊂2|2XW⊂0w→⊂→⊂ 3el c@!\v~∀$∩@@A∃→⊃↓∀b& 4T u-¬λ¬5∧πc"C!∧λλλ∧∧λ⊂siY13U∧λX∧w4\βh up by PuttindεAS\↓BAQC1hAS]MiekGβ#'?9qX4(∀∧α∧Lh8U∃"ε¬∪Hh!Q"αα∧∧αα∧9yTl,j@∧f@⎇h∀N]H≥~T→_=≤α4y`# proGpa`~AQ↑A←kQachAα{;∃β⊗KQ9LhP%↓↓∧~R2
dZmBu¬yα2≡≤
R&>p¬∧$⊂U1KX.T]CE CTLBLK[ #tA6A ⊃¬+
π%0
+1Q Jα∧
∃,L93∧@q⊃#!↓(λλ∧∧λλ∀λy3uε5⊂q∪λ&%eH↔]P⊂!Sd¬MENT That#s ppknoUnced@
$JZ∧:∪1Q Jα∧λTd∞c"A∀λλ⊂I~λ↔hλ$j⊂∃H_BE∧QdεD "MQTPUT GNE BIT";
CLπ⊂⊗6,rQαmx
d~<t
L>(⊂~~2P9|[:42iZ⎇2y;
∪'!_∞N¬@∧s#:⊃Q L,h@λ∧)lg*∩⊂'jj∀*j⊃;
~∃m!∪π%*JεtHH$&∞|j6⊗: ∧∧`-βz44[3P:7H12P $one Here.8X l4Ph ∀3Q⊂λα@ 4Jε∃α≤
N⊗M⊂h ∀h@λ∧)bbQ∞β
IN@)∃%≥β_↓!%∨π∃ +%
↓')π1$Q&u"⊗≡⊗α λλTX
@π⊂≡⊗l*0∃"λ∧p∩]⊂1w`,or f@=` βπd¬Bε6β{⊂⊗≠{tw3H3y0x~4qy]CE!"cRdε "SEP π→H@λ (!Q$9β`OR [ C
λ∧⊂∀(Yd"α*8U$≤J$#@1"@↓Hαg" ¬∩⊗αi∀`(α⊃εE